package main

import (
	"context"
	"fmt"
	"gitee.com/kaylee595/gkaylee/kerr"
	"gitee.com/kaylee595/wuaipojieCheck/internal/config"
	"gitee.com/kaylee595/wuaipojieCheck/pkg/wuaipojie"
	"github.com/imroc/req/v3"
	"github.com/samber/lo"
	"go.nhat.io/cookiejar"
	"gopkg.in/natefinch/lumberjack.v2"
	"io"
	"log/slog"
	"os"
	"strings"
)

var httpClient *req.Client

func init() {
	config.Instance = kerr.Must(config.Load())
	httpClient = config.Instance.NewHTTPClient(config.Instance.NewCookieJar())
	initLogger()
}

func initLogger() {
	writer := &lumberjack.Logger{
		Filename:  "logs/log.log",
		MaxSize:   10,
		MaxAge:    7,
		LocalTime: true,
	}
	const errKey = "err"
	logger := slog.New(slog.NewTextHandler(io.MultiWriter(writer, os.Stdout), &slog.HandlerOptions{
		AddSource: true,
		Level:     slog.LevelInfo,
		ReplaceAttr: func(groups []string, attr slog.Attr) slog.Attr {
			switch attr.Key {
			case errKey:
				err, ok := attr.Value.Any().(error)
				if !ok {
					return attr
				}
				stacks := kerr.GetTraceStacks(err)
				if len(stacks) == 0 {
					break
				}
				// 错误带跟踪栈格式化栈内容
				traces := lo.Reduce(stacks, func(agg string, item kerr.TraceStack, index int) string {
					filename := item.FileName
					nodes := strings.Split(filename, "/")
					if len(nodes) > 2 {
						l := len(nodes)
						if nodes[l-2] == "runtime" {
							return agg
						}
						filename = nodes[l-2] + "/" + nodes[l-1]
					}
					data := fmt.Sprintf("%s:%d", filename, item.Line)
					if index == 0 {
						return data
					}
					return agg + " <- " + data
				}, "")
				// 将信息包装在分组中
				attr.Value = slog.GroupValue(
					slog.String("err", err.Error()),
					slog.Any("traces", traces),
				)
			case slog.SourceKey:
				source, ok := attr.Value.Any().(*slog.Source)
				if !ok {
					break
				}
				filename := source.File
				nodes := strings.Split(filename, "/")
				if len(nodes) > 2 {
					l := len(nodes)
					filename = nodes[l-2] + "/" + nodes[l-1]
				}
				attr.Value = slog.StringValue(fmt.Sprintf("%s:%d", filename, source.Line))
			case slog.TimeKey:
				return slog.String(slog.TimeKey, attr.Value.Time().Format("01-02T15:04"))
			}
			return attr
		},
	}))
	slog.SetDefault(logger)
}

func main() {
	jar := httpClient.GetClient().Jar.(*cookiejar.PersistentJar)
	defer jar.Sync()

	err := config.Instance.NewChecker(wuaipojie.NewClient(wuaipojie.WithHttpClient(httpClient)), config.Instance.NewYesCaptcha(httpClient)).Do(context.Background())
	if err != nil {
		slog.Error("签到失败", "err", err)
		return
	}
}
